import type {
  CreateCrudOptionsProps,
  CreateCrudOptionsRet,
} from '@fast-crud/fast-crud';
import type { Dayjs } from 'dayjs';

import type { FormRulesExt } from '#/api';

import { ref } from 'vue';
import { useRouter } from 'vue-router';

import { useAccess } from '@vben/access';
import { $t } from '@vben/locales';

import { dict } from '@fast-crud/fast-crud';
import { isEmpty } from 'lodash-es';

import { asyncFindUrlById, BaseEmployeeApi, RuleType } from '#/api';
import { ExtendMsgApi } from '#/api/basic/msg/extendMsg';
import { MsgTemplateTypeEnum, SourceTypeEnum } from '#/enums/base';
import {
  ActionEnum,
  DictEnum,
  FileBizTypeEnum,
  FileBucketEnum,
  RouteEnum,
} from '#/enums/commonEnum';
import { PermCode } from '#/enums/perm';
import {
  backendDict,
  createdTimeColumn,
  deleteButton,
  indexColumn,
} from '#/plugins/fast-crud/common';
import { dateUtil } from '#/utils/dateUtil';
import { employeeCrud } from '#/views/basic/user/baseEmployee/data/common-crud';

const { hasPermission } = useAccess();
const permCode = PermCode.basic.msg.msg;

export function createCrudOptions(
  props: CreateCrudOptionsProps,
): CreateCrudOptionsRet {
  const selectedRowKeys = ref<string[]>([]);
  const menuName = RouteEnum.BASIC_MSG_ADD;
  const { push } = useRouter();
  return {
    crudOptions: {
      request: {
        pageRequest: ExtendMsgApi.pageRequest,
        addRequest: ExtendMsgApi.addRequest,
        editRequest: ExtendMsgApi.editRequest,
        delRequest: ExtendMsgApi.delRequest,
        infoRequest: ExtendMsgApi.infoRequest,
      },
      actionbar: {
        buttons: {
          add: {
            show: hasPermission(permCode.add),
            text: '发布',
            click() {
              push({
                name: menuName,
                params: { type: ActionEnum.ADD, id: '0' },
              });
            },
          },
          ...deleteButton({
            crudExpose: props.crudExpose,
            selectedRowKeys,
            removeFn: ExtendMsgApi.remove,
            role: permCode.delete,
          }),
        },
      },
      table: {
        striped: true,
        rowKey: 'id',
        rowSelection: {
          type: 'checkbox',
          selectedRowKeys,
          onChange: (changed: string[]) => {
            selectedRowKeys.value = changed;
          },
        },
      },
      rowHandle: {
        width: '200px',
        buttons: {
          edit: { show: false },
          copy: {
            dropdown: false,
            type: 'link',
            show: hasPermission(permCode.add),
            click({ row }) {
              push({
                name: menuName,
                params: { type: ActionEnum.COPY, id: row.id },
              });
            },
          },
          view: {
            show: hasPermission(permCode.view),
            click({ row }) {
              push({
                name: menuName,
                params: { type: ActionEnum.VIEW, id: row.id },
              });
            },
          },
          remove: { show: hasPermission(permCode.delete) },
        },
      },
      columns: {
        ...indexColumn(props.crudExpose),
        channel: {
          title: $t('basic.msg.extendMsg.channel'),
          type: 'text',
          form: {
            show: false,
            component: { value: SourceTypeEnum.APP },
          },
          column: {
            show: false,
          },
        },
        type: {
          title: $t('basic.msg.extendMsg.type'),
          type: 'text',
          form: {
            show: false,
            component: { value: MsgTemplateTypeEnum.NOTICE },
          },
          column: { show: false },
        },
        status: {
          title: $t('basic.msg.extendMsg.status'),
          type: 'dict-radio',
          dict: backendDict({ type: DictEnum.TaskStatus }),
          search: { show: true },
          form: { show: false },
          column: {
            width: 100,
            show: true,
          },
        },
        title: {
          title: $t('basic.msg.extendMsg.title'),
          type: 'text',
          search: { show: true },
        },
        author: {
          title: $t('basic.msg.extendMsg.author'),
          type: 'text',
          column: { width: 150 },
          search: { show: true },
        },
        remindMode: {
          title: $t('basic.msg.extendMsg.remindMode'),
          type: 'dict-radio',
          dict: backendDict(DictEnum.NoticeRemindModeEnum),
          form: {
            component: {
              optionName: 'a-radio-button',
            },
          },
          search: { show: true },
          column: { width: 100 },
        },
        recipientList: {
          title: '接收人',
          type: 'table-select',
          dict: dict({
            value: 'id',
            label: 'realName',
            getNodesByValues: async (values: any[]) => {
              return await BaseEmployeeApi.findByIds(values);
            },
          }),
          form: {
            component: {
              multiple: true,
              createCrudOptions: employeeCrud,
              crudOptionsOverride: {
                table: { scroll: { x: 2000 } },
                rowHandle: { fixed: 'right' },
              },
            },
          },
          column: {
            show: false,
          },
        },
        content: {
          title: $t('basic.msg.extendMsg.content'),
          type: 'editor-wang5',
          viewForm: { ignoreUseCellComponent: true },
          form: {
            col: { span: 24 },
            component: {
              id: '1', // 当同一个页面有多个editor时，需要配置不同的id
              config: {},
              toolbarConfig: {},
              uploader: {
                type: 'form',
                param: {
                  bucket: FileBucketEnum.public,
                  bizType: FileBizTypeEnum.EXTEND_MSG_CONTENT,
                },
                buildUrl: async (res: any) => {
                  if (res.file) {
                    return null;
                  }
                  const file = await asyncFindUrlById(res.url);
                  return file.data;
                },
              },
            },
          },
          column: { show: false },
        },
        sendTime: {
          title: $t('basic.msg.extendMsg.sendTime'),
          type: 'datetime',
          form: {
            component: {
              format: 'YYYY-MM-DD HH:mm:ss',
              valueFormat: 'YYYY-MM-DD HH:mm:ss',
              'disabled-date': (current: Dayjs): boolean => {
                return current < dateUtil().startOf('day');
              },
            },
          },
          valueBuilder({ value, row, key }) {
            if (value !== null) {
              row[key] = value;
            }
          },
          column: {
            show: true,
          },
        },
        ...createdTimeColumn({}),
      },
    },
  };
}

export const frontRules = (): FormRulesExt => {
  return {
    recipientList: {
      type: RuleType.cover,
      rules: [
        {
          trigger: 'blur',
          required: true,
          type: 'array',
          message: '请选择接收人',
        },
      ],
    },
    content: {
      type: RuleType.cover,
      rules: [
        {
          trigger: 'blur',
          required: true,
          type: 'string',

          validator: (_: any, value: string, callback) => {
            return value === '<p><br></p>'
              ? callback('请填写发送内容')
              : callback();
          },
        },
      ],
    },
    sendTime: {
      type: RuleType.cover,
      rules: [
        {
          trigger: 'blur',
          validator: (_: any, value: string, callback) => {
            return isEmpty(value) || dateUtil(value) > dateUtil().add(10, 'm')
              ? callback()
              : callback('定时发送时间至少在10分钟以后');
          },
        },
      ],
    },
  };
};
